package cn.com.zzl.util;

import org.apache.commons.lang3.StringUtils;

import java.util.Calendar;

/**
 * Description：编号规则生成器（粗糙版）
 * Created by 朱正磊 on 2017-07-04 18:12.
 */
public class CodeGenerator {

	/**
	 * 说明：CR + yyyyMM + 6位流水号，比如 CR201707000001
	 * @Desc 线索客户编号规则前缀
	 */
	public static final String CLUE_CUSTOMER_PREFIX = "CR";

	/**
	 * 说明：HHR + yyyyMMdd + 3位流水号，比如 HHR20170707001
	 * @Desc 城市合伙人编号规则前缀
	 */
	public static final String CITY_PARTNER_PREFIX = "HHR";

	/**
	 * 说明：J + yyyyMM + 3位流水号，比如 J201707001
	 * @Desc 客服记录单编号规则前缀
	 */
	public static final String RECORD_SHEET_PREFIX = "J";

	/**
	 * 说明：K + yyyyMM + 3位流水号，比如 K201707001
	 * @Desc 客诉单编号规则前缀
	 */
	public static final String COMPLAINT_PREFIX = "K";

	/**
	 * 说明：H + yyyyMM + 3位流水号，比如 H201707001
	 * @Desc 回访单编号规则前缀
	 */
	public static final String RETURN_PREFIX = "H";

	/**
	 * 说明：C + yyyyMMdd + 3位流水号，比如 C20170707001
	 * @Desc 客诉单内容编号规则前缀
	 */
	public static final String CONTENT_PREFIX = "C";

	/**
	 * 说明：F + yyyyMMdd + 3位流水号，比如 F20170707001
	 * @Desc 客诉单内容反馈编号规则前缀
	 */
	public static final String FEEDBACK_PREFIX = "F";

	/**
	 * 说明：SH + yyyyMMdd + 4位流水号，比如SH201702100001
	 * @Desc 售后回访编号前缀
	 */
	public static final String SHHF_PREFIX = "SH";

	/**
	 * 说明：TS + yyyyMMdd + 4位流水号，比如TS201702100001
	 * @Desc 投诉处理编号前缀
	 */
	public static final String TSCL_PREFIX = "TS";

	/**
	 * 说明：TD + yyyyMMdd + 4位流水号，比如TD201702100001
	 * @Desc 退订处理编号前缀
	 */
	public static final String TDCL_PREFIX = "TD";

	/**
	 * 说明：HR + yyyyMMdd + 4位流水号，比如HR201702100001
	 * @Desc 呼入跟进编号前缀
	 */
	public static final String HRGJ_PREFIX = "HR";

	/**
	 * @Desc 获取下一个流水号
	 * @param prefix 规则前缀
	 * @param maxSerialNo 最大流水号
	 * @return 返回下一个流水号
	 */
	public static String getSerialNo(String prefix, String maxSerialNo){
		String serialNo = "";
		if(StringUtils.equals(CLUE_CUSTOMER_PREFIX, prefix)){//线索客户
			if(StringUtils.isBlank(maxSerialNo)){//最大流水号不存在
				serialNo = "000001";//默认生成000001
			}else{
				serialNo = String.format("%06d", Integer.valueOf(maxSerialNo) + 1);
			}
		}else if(StringUtils.equals(CITY_PARTNER_PREFIX, prefix)//城市合伙人
				|| StringUtils.equals(RECORD_SHEET_PREFIX, prefix)//客服记录单
				|| StringUtils.equals(COMPLAINT_PREFIX, prefix)//客诉单
				|| StringUtils.equals(RETURN_PREFIX, prefix)//回访单
				|| StringUtils.equals(CONTENT_PREFIX, prefix)//客诉单内容
				|| StringUtils.equals(FEEDBACK_PREFIX, prefix)){//客诉单内容反馈
			if(StringUtils.isBlank(maxSerialNo)){//最大流水号不存在
				serialNo = "001";//默认生成001
			}else{
				serialNo = String.format("%03d", Integer.valueOf(maxSerialNo) + 1);
			}
		}else if(StringUtils.equals(SHHF_PREFIX, prefix)//售后回访
				|| StringUtils.equals(TSCL_PREFIX, prefix)//投诉处理
				|| StringUtils.equals(TDCL_PREFIX, prefix)//退订处理
				|| StringUtils.equals(HRGJ_PREFIX, prefix)){//呼入跟进
			if(StringUtils.isBlank(maxSerialNo)){//最大流水号不存在
				serialNo = "0001";//默认生成0001
			}else{
				serialNo = String.format("%04d", Integer.valueOf(maxSerialNo) + 1);
			}
		}
		return serialNo;
	}

	/**
	 * @Desc 获取规则编号
	 * @param prefix 规则前缀
	 * @param yearMonth 年月
	 * @param yearMonthDay 年月日
	 * @param serialNo 流水号
	 * @return 返回规则编号
	 */
	public static String getCode(String prefix, String yearMonth, String yearMonthDay, String serialNo){
		String code = "";
		if(StringUtils.equals(CLUE_CUSTOMER_PREFIX, prefix)//线索客户
				|| StringUtils.equals(RECORD_SHEET_PREFIX, prefix)//客服记录单
				|| StringUtils.equals(COMPLAINT_PREFIX, prefix)//客诉单
				|| StringUtils.equals(RETURN_PREFIX, prefix)){//回访单
			code = prefix + yearMonth + serialNo;
		}else if(StringUtils.equals(CITY_PARTNER_PREFIX, prefix)//城市合伙人
				|| StringUtils.equals(CONTENT_PREFIX, prefix)//客诉单内容
				|| StringUtils.equals(FEEDBACK_PREFIX, prefix)//客诉单内容反馈
				|| StringUtils.equals(SHHF_PREFIX, prefix)//售后回访
				|| StringUtils.equals(TSCL_PREFIX, prefix)//投诉处理
				|| StringUtils.equals(TDCL_PREFIX, prefix)//退订处理
				|| StringUtils.equals(HRGJ_PREFIX, prefix)){//呼入跟进
			code = prefix + yearMonthDay + serialNo;
		}
		return code;
	}

	/**
	 * @Desc 获取年月
	 * @return 返回格式 yyyyMM
	 */
	public static String getCurrentYearMonth(){
		Calendar calendar = Calendar.getInstance();
		int year = calendar.get(Calendar.YEAR);
		int month = calendar.get(Calendar.MONTH) + 1;
		return year + "" + ( month < 10 ? "0" + month : month);
	}

	/**
	 * @Desc 获取年月日
	 * @return 返回格式 yyyyMMdd
	 */
	public static String getCurrentYearMonthDay(){
		Calendar calendar = Calendar.getInstance();
		int year = calendar.get(Calendar.YEAR);
		int month = calendar.get(Calendar.MONTH) + 1;
		int day = calendar.get(Calendar.DAY_OF_MONTH);
		return year + "" + (month < 10 ? "0" + month : month) + "" + (day < 10 ? "0" + day : day);
	}

	/**
	 * @Desc 获取与规则编号相关的数据数组
	 * @param prefix 前缀
	 * @param object 对象
	 * @param methodName 方法名
	 * @param mapper mapper方法名
	 * @return 返回值是一个code、dateNum、serialNo组成的字符串数组
	 */
	public static String[] getCodeInfo(String prefix, Object object, String methodName, String mapper){
		String yearMonth = getCurrentYearMonth();
		String yearMonthDay = getCurrentYearMonthDay();
		Class<?>[] classes = new Class[]{String.class, Object.class};
		Object[] params = new Object[2];
		params[0] = mapper;
		if(StringUtils.equals(CLUE_CUSTOMER_PREFIX, prefix)//线索客户
				|| StringUtils.equals(RECORD_SHEET_PREFIX, prefix)//客服记录单
				|| StringUtils.equals(COMPLAINT_PREFIX, prefix)//客诉单
				|| StringUtils.equals(RETURN_PREFIX, prefix)){//回访单
			params[1] = yearMonth;
		}else if(StringUtils.equals(CITY_PARTNER_PREFIX, prefix)//城市合伙人
				|| StringUtils.equals(CONTENT_PREFIX, prefix)//客诉单内容
				|| StringUtils.equals(FEEDBACK_PREFIX, prefix)//客诉单内容反馈
				|| StringUtils.equals(SHHF_PREFIX, prefix)//售后回访
				|| StringUtils.equals(TSCL_PREFIX, prefix)//投诉处理
				|| StringUtils.equals(TDCL_PREFIX, prefix)//退订处理
				|| StringUtils.equals(HRGJ_PREFIX, prefix)){//呼入跟进
			params[1] = yearMonthDay;
		}
		String maxSerialNo = (String) ReflectUtil.invoke(object, methodName, classes, params);
		String serialNo = getSerialNo(prefix, maxSerialNo);
		String code = "";//规则编号
		String dateNum = "";//日期数字
		if(StringUtils.equals(CLUE_CUSTOMER_PREFIX, prefix)//线索客户
				|| StringUtils.equals(RECORD_SHEET_PREFIX, prefix)//客服记录单
				|| StringUtils.equals(COMPLAINT_PREFIX, prefix)//客诉单
				|| StringUtils.equals(RETURN_PREFIX, prefix)){//回访单
			code = getCode(prefix, yearMonth, null, serialNo);
			dateNum = yearMonth;
		}else if(StringUtils.equals(CITY_PARTNER_PREFIX, prefix)//城市合伙人
				|| StringUtils.equals(CONTENT_PREFIX, prefix)//客诉单内容
				|| StringUtils.equals(FEEDBACK_PREFIX, prefix)//客诉单内容反馈
				|| StringUtils.equals(SHHF_PREFIX, prefix)//售后回访
				|| StringUtils.equals(TSCL_PREFIX, prefix)//投诉处理
				|| StringUtils.equals(TDCL_PREFIX, prefix)//退订处理
				|| StringUtils.equals(HRGJ_PREFIX, prefix)){//呼入跟进
			code = getCode(prefix, null, yearMonthDay, serialNo);
			dateNum = yearMonthDay;
		}
		return new String[]{code, dateNum, serialNo};
	}

	/**
	 * @Desc 测试编号规则生成方式是否正确
	 * @param args main默认参数
	 */
	public static void main(String[] args) {
		String prefix = CodeGenerator.CLUE_CUSTOMER_PREFIX;
		//第一次为null（从数据库里根据条件查流水号，不建议使用count(*)来查询因为数据有删减，建议使用max()函数）
		String maxSerialNo = "000001";
		String serialNo = CodeGenerator.getSerialNo(prefix, maxSerialNo);
		String yearMonth = CodeGenerator.getCurrentYearMonth();
		String code = CodeGenerator.getCode(prefix, yearMonth, null, serialNo);
		System.out.println(code);

		String prefix2 = CodeGenerator.CITY_PARTNER_PREFIX;
		//第一次为null（从数据库里根据条件查流水号，不建议使用count(*)来查询因为数据有删减，建议使用max()函数）
		String maxSerialNo2 = "001";
		String serialNo2 = CodeGenerator.getSerialNo(prefix2, maxSerialNo2);
		String yearMonthDay = CodeGenerator.getCurrentYearMonthDay();
		String code2 = CodeGenerator.getCode(prefix2, null, yearMonthDay, serialNo2);
		System.out.println(code2);

		//String[] complaintCodeInfo = getCodeInfo(COMPLAINT_PREFIX, daoSupport, "findForObject", "ComplaintMapper.findMaxSerialNo");
	}

}
